#necesarios
from django.shortcuts import get_object_or_404, render_to_response
from django.http import HttpResponseRedirect, HttpResponse
from django.core.urlresolvers import reverse
from django.template import RequestContext
#modelos
from django.db.models import Q
from auth.models import User
from models import Grupo

#funcionalidad general
from django.forms.models import modelformset_factory
from django import forms
from django.forms import ModelForm
from auth import logout
from auth.decorators import permission_required
from auth import authenticate,login
from auth.decorators import login_required

#ajax
from django.core.paginator import Paginator, InvalidPage, EmptyPage
from django.core.serializers import serialize

from django.core.exceptions import ObjectDoesNotExist

#Metodo que recibe la informacion de autenticacion,
#determina si es correcta y en caso de serlo marca
#al usuario actual como autenticado
class LoginForm(forms.Form):
    password = forms.CharField(required=True,help_text='Una contrase&ntilde;a v&aacute;lida')
    usuario = forms.CharField(required=True)    

def enter(request):
    fallo_en_login = False
    if request.method == 'POST':
        form = LoginForm(request.POST)
        nombreusuario = form.data['usuario']        
        contrasena = form.data['password']        
        
        if form.is_valid():
            usuario_autenticado = authenticate(username=nombreusuario,password=contrasena)
            if usuario_autenticado is not None:
                success = True
                login(request,usuario_autenticado)
                return HttpResponseRedirect('/core/menu')
            else:
                fallo_en_login = True
    else:
        form = LoginForm()
        nombreusuario = ''
        contrasena = ''

    return render_to_response('core/login.html',{
                'form': form,
                'usuario': nombreusuario,
                'password': contrasena,
                'fallo_en_login': fallo_en_login
                }, context_instance=RequestContext(request))

class GrupoForm(forms.Form):
    nombre = forms.CharField(max_length=25,required=True)
    #es_privado = forms.BooleanField(required=False)

@login_required
def crear_grupo(request):
    if request.method == 'POST':
        form = GrupoForm(request.POST)

        if form.is_valid():
            admin = request.user
            convertir_a_miembro = lambda username: User.objects.get(username=username)
            miembros = map(convertir_a_miembro,request.POST.getlist('miembros'))
            nombre_del_grupo = form.cleaned_data['nombre']
            #es_privado = form.cleaned_data['es_privado']
            #nuevo_grupo = Grupo.objects.create(nombre=nombre_del_grupo,es_privado=es_privado,administrador=admin)            
            nuevo_grupo = Grupo.objects.create(nombre=nombre_del_grupo,administrador=admin)            
            #guardar nuevo grupo
            nuevo_grupo.save()
            miembros.append(admin)
            for miembro in miembros:
                nuevo_grupo.miembros.add(miembro)

            return HttpResponseRedirect('/core/ver_grupo/?grupo='+nombre_del_grupo)
        else:
            return render_to_response('core/crear_grupo.html',{
                    'form': form
                    },context_instance=RequestContext(request))
    else:
        return crear_nuevo_grupo(request)
    

#Despliega un menu que permite al usuario autenticarse
#Luego de que el usuario haya ingresado los datos, estos
#son enviados a la vista enter
def ingresar(request):
    titulo = "Identificate"
    if request.user.is_authenticated():
        return HttpResponseRedirect('/core/menu')

    return render_to_response('core/login.html',context_instance=RequestContext(request, locals()))

#Vista que se encarga de desautenticar al usuario acutal,
#si es llamada el usuario actual ya no estara autenticado
@login_required()
def salir(request):
    logout(request)
    return HttpResponseRedirect('/core/ingresar')

#Despliega el menu principal de campus movil pro
@login_required()
def menu(request):
    usuario=request.user
    return render_to_response('core/menu.html', {'usuario': usuario}, context_instance=RequestContext(request, {}))

#Despliega la platnilla que permite que el usuario modifique
#su configuracion
@login_required()
def configuracion(request):
    usuario=request.user
    return render_to_response('core/configuracion.html', {'usuario' : usuario}, context_instance=RequestContext(request, {}))

#Vista que analiza los cambios realizados por el usuario y 
#actualiza el modelo en la base de datos.
@login_required()
def cambiar_configuracion(request):
    if request.method != 'POST':
        return HttpResponseRedirect('/core/configuracion')
        
    usuario=request.user
    if request.POST['clave_nueva']!='':

        clave=request.POST['clave']
        if authenticate(username=usuario.username, password=clave) is not None:
            if request.POST['clave_nueva']==request.POST['clave_nueva1']:
                usuario.set_password(request.POST['clave_nueva'])
                usuario.save()
                return HttpResponseRedirect('/core/menu')

    return HttpResponseRedirect('/core/configuracion')
        

#Vista que lista a los grupos, si el usuario esta identificado (logueado)
#autor: kmels
@login_required()
def listar_grupos(request):
    lista_de_grupos = Grupo.objects.all()
    paginator = Paginator(lista_de_grupos, 5) # Mostrar 5 grupos por pagina
    titulo = "Listado de grupos"
    
    # Make sure page request is an int. If not, deliver first page.
    try:
        pagina = int(request.GET.get('pagina', '1'))
    except ValueError:
        pagina = 1

    # If page request (9999) is out of range, deliver last page of results.
    try:
        grupos = paginator.page(pagina)
    except (EmptyPage, InvalidPage):
        grupos = paginator.page(paginator.num_pages)

    return render_to_response('core/lista_grupos.html', locals())


#Vista de detalle de un grupo
#autor: kmels
@login_required()
def ver_grupo(request):
    nombre_del_grupo = request.GET['grupo']
    grupo = Grupo.objects.get(nombre=nombre_del_grupo)
    
    #Verificacion con respecto a private key de los usuarios
    esAdmin = request.user.pk is grupo.administrador.pk
        
    return render_to_response('core/ver_grupo.html', {"grupo": grupo, "esAdmin": esAdmin})

#formulario para crear un nuevo grupo
#autor: kmels
@login_required()
def crear_nuevo_grupo(request):
    return render_to_response('core/crear_grupo.html',context_instance=RequestContext(request))

def buscar_usuario(request):
    query = request.GET['q']
    lista_de_usuarios = User.objects.filter(Q(username__istartswith=query) | Q(first_name__istartswith=query))
    
    json = serialize("json",lista_de_usuarios.order_by("username")[:10])        #json = serialize("json",lista_de_usuarios[:10])    
    #    if request.is_ajax():
    return HttpResponse(json,mimetype="application/x-javascript")
  
#Vista de eliminar grupo
#autor: hectorh30
@login_required()
def eliminar_grupo(request):
	pk_del_grupo = request.GET['grupo']
	
	try:
	  grupo = Grupo.objects.get(pk=pk_del_grupo)
	except ObjectDoesNotExist:
	  return render_to_response('core/menu.html',{"error": "Grupo inexistente","usuario": request.user})

	if(grupo.administrador.pk == request.user.pk):
		grupo.delete()
		return render_to_response('core/menu.html',{"grupo_eliminado": grupo.nombre, "usuario": request.user})
	else:
		return render_to_response('core/menu.html',{"error": "No tiene permisos para elimnar este grupo","usuario": request.user})

#menu de grupos
#autor kmels
@login_required
def menu_grupos(request):
    return render_to_response('core/menu_grupos.html',locals())

#mis grupos
#autor kmels
@login_required()
def mis_grupos(request):
    usuario=request.user
    lista_de_grupos = Grupo.objects.filter(administrador=usuario)    
    paginator = Paginator(lista_de_grupos, 5) # Mostrar 5 grupos por pagina
    
    # Make sure page request is an int. If not, deliver first page.
    try:
        pagina = int(request.GET.get('pagina', '1'))
    except ValueError:
        pagina = 1

    # If page request (9999) is out of range, deliver last page of results.
    try:
        grupos = paginator.page(pagina)
    except (EmptyPage, InvalidPage):
        grupos = paginator.page(paginator.num_pages)

    return render_to_response('core/lista_grupos.html', locals())

